package by.sjc.giz.web.controller;

import by.sjc.giz.model.*;
import by.sjc.giz.model.publisher.BooksWithMaxCount;
import by.sjc.giz.model.publisher.ContractWithAuthors;
import by.sjc.giz.model.publisher.Discount;
import by.sjc.giz.model.publisher.Publisher;
import by.sjc.giz.security.CustomUserDetails;
import by.sjc.giz.service.*;
import org.apache.log4j.Logger;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.security.core.Authentication;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.servlet.ModelAndView;

import javax.servlet.http.HttpSession;
import java.util.Date;
import java.util.List;

/**
 * Created by Z on 11.08.14.
 */
@Controller
@RequestMapping("/publisher")
public class PublisherController {

    public static final Logger logger = Logger.getLogger(PublisherController.class);

    @Autowired
    AccountService accountService;
    @Autowired
    PublisherService publisherService;
    @Autowired
    SubjectService subjectService;
    @Autowired
    OrderService orderService;
    @Autowired
    BookService bookService;

    @RequestMapping(value = {"/{id}"})
    public ModelAndView publisherInfo(
            @PathVariable("id") Subject publisher) {

        ModelAndView mav = new ModelAndView();
        mav.setViewName("publisher.info");
        mav.addObject(publisher);
        return mav;
    }

    @RequestMapping(value = {"/list"})
    public ModelAndView listPublishers() {
        List<Subject> publisherList =  publisherService.getPublisherList();

        ModelAndView mav = new ModelAndView();
        mav.setViewName("publisher.list");
        mav.addObject("publishers", publisherList);
        return mav;
    }


    @PreAuthorize("isFullyAuthenticated() and principal.account.subject.type.value == 'PUBLISHER'")
    @RequestMapping(value = {"/employees"})
    public ModelAndView listEmployees(Authentication authentication) {
        Subject publisher = ((CustomUserDetails) authentication.getPrincipal()).getAccount().getSubject();
        List<Account> employees = accountService.getSubjectAccounts(publisher.getId());
        logger.info("list employees for " + publisher + ":");
        logger.info(employees.toString());

        ModelAndView mav = new ModelAndView();
        mav.setViewName("employeesList");
        mav.addObject("employees",employees);
        mav.addObject("employer",publisher);
        return mav;
    }

    @PreAuthorize("isFullyAuthenticated() and principal.account.subject.type.value == 'PUBLISHER'")
    @RequestMapping(value={"/contracts"})
    public ModelAndView listContracts(Authentication authentication) {
        Subject publisher = ((CustomUserDetails) authentication.getPrincipal()).getAccount().getSubject();
        List<ContractWithAuthors> contracts = publisherService.getContractWithAuthorsList(publisher.getId());

        ModelAndView mav = new ModelAndView();
        mav.setViewName("publisher.contracts");
        mav.addObject("contracts",contracts);
        mav.addObject("publisher",publisher);

        return mav;
    }

    @PreAuthorize("isFullyAuthenticated() and principal.account.subject.type.value == 'PUBLISHER'")
    @RequestMapping(value={"/addBook"},  method = { RequestMethod.GET })
    public ModelAndView addBook(Authentication authentication ) {
        Subject publisher = ((CustomUserDetails) authentication.getPrincipal()).getAccount().getSubject();

        ContractWithAuthors contract = new ContractWithAuthors();
        contract.getBook().setReleaseDate(new Date());
        List<String> genres = bookService.getAllGenres();
        List<String> authors = bookService.getAllAuthors();

        ModelAndView mav = new ModelAndView();
        mav.setViewName("publisher.addBook");
        mav.addObject("publisher",publisher);
        mav.addObject("contract", contract);
        mav.addObject("genres",genres);
        mav.addObject("authors",authors);
        return mav;
    }

    @PreAuthorize("isFullyAuthenticated() and principal.account.subject.type.value == 'PUBLISHER'")
    @RequestMapping(value={"/addBook"},  method = { RequestMethod.POST })
    public ModelAndView addBook(
            Authentication authentication,
            ContractWithAuthors contract) {
        Subject publisher = ((CustomUserDetails) authentication.getPrincipal()).getAccount().getSubject();

        contract.getBook().setPublisher((Publisher) publisher);

        logger.info(contract);
        publisherService.addContractWithAuthors(contract);
        ModelAndView mav = new ModelAndView();
        mav.setViewName("redirect:/publisher/" + publisher.getId() + "/books");
        return mav;
    }

    @RequestMapping(value = {"/{id}/books"})
    public ModelAndView listPublisherBooks(
            @PathVariable("id") Subject publisher,
            @RequestParam(value = "pageNum",defaultValue = "1") int pageNum,
            @RequestParam(value = "pageSize",defaultValue = "5") int pageSize,
            BooksFilter filter  ) {

        logger.info("filter by publisher" + publisher);
        if (publisher.getType() != SubjectType.PUBLISHER)
            return new ModelAndView("redirect:/publisher/list");

        if (filter==null)
            filter = new BooksFilter();
        logger.info("filter : "+filter);
        filter.setPublisher(publisher.getName());

        BooksWithMaxCount res = publisherService.getBooks(pageSize,pageNum,filter);

        List<String> allGenres = bookService.getAllGenres();
        List<String> allAuthors = bookService.getAllAuthors();

        ModelAndView mav = new ModelAndView();
        mav.setViewName("publisher.books");

        mav.addObject("contracts",res.getContracts());

        mav.addObject("publisher", publisher);
        mav.addObject("allGenres",allGenres);
        mav.addObject("allAuthors",allAuthors);
        mav.addObject("filter",filter);

        mav.addObject("pageCount", res.getPageCount(pageSize));
        mav.addObject("pageNum",pageNum);
        mav.addObject("pageSize",pageSize);

        return mav;
    }


    @RequestMapping(value = {"/books"})
    public ModelAndView listAllBooks(
            @RequestParam(value = "pageNum",defaultValue = "1") int pageNum,
            @RequestParam(value = "pageSize",defaultValue = "5") int pageSize,
            BooksFilter filter ) {

        if (filter==null)
            filter = new BooksFilter();
        logger.info("filter : "+filter);


        BooksWithMaxCount res = publisherService.getBooks(pageSize,pageNum,filter);

        List<String> allGenres = bookService.getAllGenres();
        List<String> allAuthors = bookService.getAllAuthors();
        List<String> allPublishers = bookService.getAllPublishers();

        ModelAndView mav = new ModelAndView();
        mav.setViewName("publisher.books");

        mav.addObject("contracts",res.getContracts());

        mav.addObject("allGenres",allGenres);
        mav.addObject("allAuthors",allAuthors);
        mav.addObject("allPublishers",allPublishers);

        mav.addObject("filter",filter);

        mav.addObject("pageCount", res.getPageCount(pageSize));
        mav.addObject("pageNum",pageNum);
        mav.addObject("pageSize",pageSize);

        return mav;
    }

    @PreAuthorize("isFullyAuthenticated() and principal.account.subject.type.value == 'PUBLISHER'")
    @RequestMapping(value={"/discounts"})
    public ModelAndView listDiscounts(Authentication authentication) {
        Subject publisher = ((CustomUserDetails) authentication.getPrincipal()).getAccount().getSubject();

        List<Discount> discounts = publisherService.getDiscountList(publisher,-1,0);
        ModelAndView mav = new ModelAndView();
        mav.setViewName("publisher.discounts");

        mav.addObject("publisher",publisher);
        mav.addObject("discounts",discounts);
        return mav;
    }

    @PreAuthorize("isFullyAuthenticated() and principal.account.subject.type.value == 'PUBLISHER'")
    @RequestMapping(value={"/admin"})
    public ModelAndView adminPage(Authentication authentication) {
        Subject publisher = ((CustomUserDetails) authentication.getPrincipal()).getAccount().getSubject();
        ModelAndView mav = new ModelAndView();
        mav.setViewName("publisher.admin");
        mav.addObject("publisher",publisher);
        return mav;
    }

}
